#pragma once
#include <iostream>
#include <string>
#include <jsoncpp/json/json.h>
using namespace std;

static const string BLANK_STRING = " ";
static const string PROTOCOL_SEP = "\n";

static string encode(const string& text)
{
    // 添加报头
    string ret = to_string(text.size());
    ret += PROTOCOL_SEP;
    ret += text;
    ret += PROTOCOL_SEP;
    return ret;
}

static bool decode(string& text, string* out)
{
    // 移除报头   "len\n""a op b\n"???
    size_t pos = text.find(PROTOCOL_SEP);
    if(pos == string::npos)    return false;
    string headStr = text.substr(0, pos);
    size_t textLen = stoi(headStr);
    size_t totalLen = textLen + 2 + headStr.size();
    // text可能除了"len\na op b\n"外增加了其它字符，比如"len\na op b\nlen\n..."。这里拿取了一个完整的
    if(text.size() < totalLen)  return false;
    *out = text.substr(pos+1, textLen);
    // 移除这一个完整的报文，防止text越来越大
    text.erase(0, totalLen);
    return true;
}

struct Request
{
    int _a;
    int _b;
    char _op;
    Request(int a, int b, char op) : _a(a), _b(b), _op(op) {}
    Request() {}

    bool serialize(string* out)
    {   
#ifdef MYSELF
        // 构建有效载荷，将成员属性变为 "_a op _b"
        string tmp = to_string(_a);
        tmp += BLANK_STRING;
        tmp += _op;
        tmp += BLANK_STRING;
        tmp += to_string(_b);
        *out = tmp;
        return true;
#else 
        Json::Value tmp;
        tmp["x"] = _a;
        tmp["op"] = _op;
        tmp["y"] = _b;
        Json::FastWriter w;
        *out = w.write(tmp);
        return true;
#endif
    }

    bool deserialize(const string& in)
    {
#ifdef MYSELF
        // 反序列化 将"_a op _b"拆分
        size_t left = in.find(BLANK_STRING);
        if(left == string::npos)    {
            cerr << "if(left == string::npos) err" << endl;
            return false;
        }
        _a = stoi(in.substr(0, left));

        size_t right = in.rfind(BLANK_STRING);
        if(right == string::npos)   {
            cerr << "if(right == string::npos) err" << endl;
            return false;
        }
        _b = stoi(in.substr(right+1));

        if(left + 2 != right)   {
            cerr << "if(left + 2 != right) err" << endl;
            return false;
        }
        _op = in[left+1];
        return true;
#else 
        Json::Value v;
        Json::Reader r;
        r.parse(in, v);
        _a = v["x"].asInt();
        _op = v["op"].asInt();
        _b = v["y"].asInt();
        return true;
#endif
    }

    void printInfo()
    {
        printf("%d %c %d = ?\n", _a, _op, _b);
    }
};

struct Response
{
    int _res;
    int _exitCode = 0;      // 0 表示可信
    Response(int res, int exitCode) : _res(res), _exitCode(exitCode) {}
    Response() {}
    
    bool serialize(string* out)
    {   
#ifdef MYSELF
        // 构建有效载荷，将成员属性变为 "_res op _exitCode"
        string tmp = to_string(_res);
        tmp += BLANK_STRING;
        tmp += to_string(_exitCode);
        *out = tmp;
        return true;
#else 
        Json::Value tmp;
        tmp["res"] = _res;
        tmp["code"] = _exitCode;
        Json::FastWriter w;
        *out = w.write(tmp);
        return true;
#endif
    }

    bool deserialize(const string& in)
    {
#ifdef MYSELF
        // 反序列化 将"_res op _exitCode"拆分
        size_t left = in.find(BLANK_STRING);
        if(left == string::npos)    return false;
        _res = stoi(in.substr(0, left));
        _exitCode = stoi(in.substr(left+1));
#else
        Json::Value v;
        Json::Reader r;
        r.parse(in, v);
        _res = v["res"].asInt();
        _exitCode = v["code"].asInt();
        return true;
#endif
    }

    void printInfo()
    {
        printf("exitCode: %d, res: %d\n", _exitCode, _res);
    }
};


